package com.catazzz.springbootstudy.common;

import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;

/**
 * @作者: Tao
 * @日期: 2024/12/24
 * @时间: 18:08
 * @描述: 记录时间拦截器类
 */
@Slf4j
@Component
public class TimeInterceptor implements HandlerInterceptor {

    private final ThreadLocal<LocalTime> startTime = new ThreadLocal<>();
    private final ThreadLocal<LocalTime> endTime = new ThreadLocal<>();

    private final DateTimeFormatter formatter = DateTimeFormatter.ofPattern("HH:mm:ss:SSSS");

    /**
     * 请求处理前的方法
     * 该方法在请求处理前被调用，用于记录请求开始时的日志信息
     *
     * @param request  HttpServletRequest对象，包含请求相关的信息
     * @param response HttpServletResponse对象，包含响应相关的信息
     * @param handler  请求处理者对象，可以是处理器方法或处理器实例
     * @return boolean 表示是否继续执行其他拦截器和处理器方法，true表示继续执行
     * @throws Exception 如果处理过程中发生异常，则抛出此异常
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        startTime.set(LocalTime.now());
        log.info("开始时间--->{}", startTime.get().format(formatter));
        return true;
    }

    /**
     * 请求处理后的方法
     * 该方法在请求处理后被调用，用于记录请求处理完成后的日志信息
     *
     * @param request      HttpServletRequest对象，包含请求相关的信息
     * @param response     HttpServletResponse对象，包含响应相关的信息
     * @param handler      请求处理者对象，可以是处理器方法或处理器实例
     * @param modelAndView ModelAndView对象，包含模型和视图的信息
     * @throws Exception 如果处理过程中发生异常，则抛出此异常
     */
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        endTime.set(LocalTime.now());
        log.info("结束时间--->{}", endTime.get().format(formatter));
    }

    /**
     * 请求完全处理完毕后的方法
     * 该方法在请求处理完全完成后被调用，无论是否异常终止，用于记录请求完全处理完毕后的日志信息
     *
     * @param request  HttpServletRequest对象，包含请求相关的信息
     * @param response HttpServletResponse对象，包含响应相关的信息
     * @param handler  请求处理者对象，可以是处理器方法或处理器实例
     * @param ex       请求处理过程中发生的异常，如果没有异常，则为null
     * @throws Exception 如果处理过程中发生异常，则抛出此异常
     */
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        log.info("请求处理时间--->{}", startTime.get().until(endTime.get(), ChronoUnit.MILLIS));
    }
}

